<template>
    <div class="root">
        <div class="container-shell">
            <div id="container" ref="container"></div>
            <!-- 对讲 -->
            <div class="trank-wrap" v-if="type === 1">
                <el-tooltip :content="broadcastTooltip.content" placement="top" v-if="showBroadcastTooltip">
                    <i class="el-icon-mic" @click="broadcastStatusClick()" :disabled="broadcastStatus === -2"></i>
                </el-tooltip>
            </div>
            <!-- 自定义倍速控制按钮 -->
            <el-dropdown class="playback-rate-control" trigger="click" @command="handleRateChange" v-if="type === 2">
                <el-button type="text" style="color: #fff">
                    {{ currentRate }}x
                    <i class="fa fa-caret-down"></i>
                </el-button>
                <el-dropdown-menu slot="dropdown">
                    <el-dropdown-item v-for="rate in rateOptions" :key="rate" :command="rate" :class="{ selected: currentRate === rate }">{{ rate }}x</el-dropdown-item>
                </el-dropdown-menu>
            </el-dropdown>
        </div>
    </div>
</template>

<script>
let jessibucaPlayer = {};
import { ptzdirection, ptzscale } from '@/api/iot/sipdevice';
import { getPushUrl, listChannel, startBroadcast, stopBroadcast, playbackSpeed } from '@/api/iot/channel';

export default {
    name: 'player',
    props: {
        playerinfo: {
            type: Object,
            default: null,
        },
        channelId: {
            type: String,
            default: '',
        },
        deviceId: {
            // 设备id
            type: String,
            default: '',
        },
        streamId: {
            type: String,
            default: '',
        },
    },
    computed: {
        showBroadcastTooltip() {
            return [-1, -2, 0, 1].includes(this.broadcastStatus);
        },
        broadcastTooltip() {
            const statusMap = {
                [-1]: { content: this.$t('views.components.player.webrtc.08878-3') },
                [-2]: { content: this.$t('views.components.player.webrtc.08878-2') },
                [0]: { content: this.$t('views.components.player.webrtc.08878-4') },
                [1]: { content: this.$t('views.components.player.webrtc.08878-5') },
            };
            return statusMap[this.broadcastStatus] || {};
        },
    },
    mounted() {
        console.log(this._uid);
    },
    watch: {
        playerinfo: function (newVal, oldVal) {
            console.log('playerinfo 发生变化');
            this.playinfo = newVal;
            if (this.playinfo && this.playinfo.playtype !== '') {
                this.playtype = this.playinfo.playtype;
            }
        },
    },
    jessibuca: null,
    data() {
        return {
            isPlaybackPause: false,
            playbackStartTime: 0,
            useWebGPU: false,
            isInit: false,
            playinfo: {},
            playtype: 'play',
            operateBtns: {
                fullscreen: true,
                zoom: true,
                play: true,
                audio: true,
            },
            broadcastRtc: null,
            broadcastStatus: -1, // -2 正在释放资源 -1 默认状态 0 等待接通 1 接通成功
            isSpeedMenuOpen: false, // 速度菜单是否打开
            currentRate: 1.0, // 当前倍速
            rateOptions: [1, 2, 4], // 倍速选项
            type: 0, //0默认，1直播（显示对讲按钮），2录像回放（显示倍速菜单）
        };
    },
    created() {
        this.playinfo = this.playerinfo;
        if (this.playinfo && this.playinfo.playtype !== '') {
            this.playtype = this.playinfo.playtype;
        }
        this.init();
    },
    methods: {
        init() {
            var isSupportWebgpu = 'gpu' in navigator;
            if (isSupportWebgpu) {
                console.log('支持webGPU');
                this.useWebGPU = true;
            } else {
                console.log('暂不支持webGPU，降级到webgl渲染');
                this.useWebGPU = false;
            }

            const useVconsole = this.isMobile() || this.isPad();
            if (useVconsole && window.VConsole) {
                new window.VConsole();
            }
            this.$nextTick(() => {
                this.initplayer();
            });
        },

        // 倍速播放处理
        async handleRateChange(rate) {
            console.log('handleRateChange', rate);
            this.currentRate = rate;
            try {
                const query = {
                    speed: rate,
                };
                playbackSpeed(this.deviceId, this.channelId, this.streamId, query).then((res) => {
                    if (res.code === 200) {
                        let streamInfo = res.data;
                    } else {
                        this.$message({
                            showClose: true,
                            message: res.msg,
                            type: 'error',
                        });
                    }
                });
            } catch (error) {
                console.error('倍速设置失败:', error);
                this.$message.error('倍速设置保存失败');
            }
        },

        initplayer() {
            this.isPlaybackPause = false;
            this.initconf();
            jessibucaPlayer[this._uid] = new window.JessibucaPro({
                container: this.$refs.container,
                decoder: '/js/jessibuca-pro/decoder-pro.js',
                videoBuffer: Number(0.2), // 缓存时长
                isResize: false,
                useWCS: false,
                useMSE: false,
                useSIMD: true,
                wcsUseVideoRender: false,
                loadingText: '加载中',
                debug: false,
                debugLevel: 'debug',
                showBandwidth: true, // 显示网速
                showPlaybackOperate: true,
                operateBtns: this.operateBtns,
                forceNoOffscreen: true,
                isNotMute: true, // 默认关闭声音
                showPerformance: false,
                // playFailedAndReplay: true,
                // networkDelayTimeoutReplay: true,
                playbackForwardMaxRateDecodeIFrame: 4,
                useWebGPU: this.useWebGPU, // 使用WebGPU
            });
            let jessibuca = jessibucaPlayer[this._uid];
            this.initcallback(jessibuca);
            this.isInit = true;
        },
        // 切换速度菜单显示状态
        toggleSpeedMenu() {
            this.isSpeedMenuOpen = !this.isSpeedMenuOpen;
        },

        initconf() {
            if (this.playtype === 'play') {
                //直播按钮配置
                this.operateBtns.ptz = true;
            } else {
                //录像回放按钮配置
                this.operateBtns.ptz = false;
            }
        },
        initcallback(jessibuca) {
            const _this = this;
            jessibuca.on('error', function (error) {
                console.log('jessibuca error');
                console.log(error);
                //_this.destroy();
            });
            jessibuca.on('playFailedAndPaused', function (reason, lastFrameInfo, msg) {
                console.log('playFailedAndPaused', reason, msg);
                // lastFrameInfo 是最后一帧的画面，可以用来重播的时候，显示最后一帧画面。
                // msg 具体的错误信息。
            });
            jessibuca.on('visibilityChange', (value) => {
                if (value === true) {
                    // 窗口显示
                    console.log('visibilityChange true');
                } else {
                    // 窗口隐藏
                    console.log('visibilityChange false');
                }
            });
            jessibuca.on('pause', function (pause) {
                console.log('pause success!');
                console.log(pause);
            });
            jessibuca.on('play', function (flag) {
                if (_this.playtype === 'play') {
                    _this.type = 1;
                } else {
                    _this.type = 2;
                }
                console.log('play!');
                console.log(flag);
                // 更新进度条
                if (_this.playtype === 'playback') {
                  console.log('on playback play: [' + _this.playbackStartTime + ']');
                  jessibuca.setPlaybackStartTime(_this.playbackStartTime);
                }
            });
            jessibuca.on('loading', function (load) {
                console.log('loading success!');
                console.log(load);
            });
            jessibuca.on('stats', function (s) {
                // console.log('stats is', s);
            });
            jessibuca.on('timeout', function (error) {
                console.log('timeout:', error);
            });
            jessibuca.on('playbackPreRateChange', (rate) => {
                jessibuca.forward(rate);
            });

            let pre = 0;
            let cur = 0;
            jessibuca.on('timeUpdate', function (ts) {
                cur = parseInt(ts / 60000);
                if (pre !== cur) {
                    pre++;
                }
            });
            jessibuca.on(JessibucaPro.EVENTS.ptz, (arrow) => {
                console.log('ptz arrow', arrow);
                _this.handlePtz(arrow);
            });
            jessibuca.on('crashLog', (data) => {
                console.log('crashLog is', data);
            });
        },
        registercallback(events, func) {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].on(events, func);
            }
        },
        isMobile() {
            return /iphone|ipad|android.*mobile|windows.*phone|blackberry.*mobile/i.test(window.navigator.userAgent.toLowerCase());
        },
        isPad() {
            return /ipad|android(?!.*mobile)|tablet|kindle|silk/i.test(window.navigator.userAgent.toLowerCase());
        },
        play(url) {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].play(url);
            }
        },
        pause() {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].pause();
            }
        },
        replay(url) {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].destroy().then(() => {
                    this.initplayer();
                    this.play(url);
                });
            } else {
                this.initplayer();
                this.play(url);
            }
        },
        handlePtz(arrow) {
            let leftRight = 0;
            let upDown = 0;
            if (arrow === 'left') {
                leftRight = 2;
            } else if (arrow === 'right') {
                leftRight = 1;
            } else if (arrow === 'up') {
                upDown = 1;
            } else if (arrow === 'down') {
                upDown = 2;
            }
            var data = {
                leftRight: leftRight,
                upDown: upDown,
                moveSpeed: 125,
            };
            if (this.playinfo && this.playinfo.playtype !== '') {
                ptzdirection(this.playinfo.deviceId, this.playinfo.channelId, data).then(async (response) => {
                    //console.log("云台方向控制：" + JSON.stringify(response));
                });
            }
        },
        playback(url, playTimes) {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].playback(url, {
                    playList: playTimes,
                    fps: 25, //FPS（定频(本地设置)生效）
                    showControl: true,
                    isUseFpsRender: true, // 是否使用固定的fps渲染，如果设置的fps小于流推过来的，会造成内存堆积甚至溢出
                    isCacheBeforeDecodeForFpsRender: false, // rfs渲染时，是否在解码前缓存数据
                    supportWheel: true, // 是否支持滚动轴切换精度。
                });
                this.isPlaybackPause = false;
            }
        },
        playbackPause() {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].playbackPause();
                this.isPlaybackPause = true;
            }
        },

        beforeDestroy() {
            // 销毁播放器释放资源
            if (this.player) {
                this.player.destroy();
                this.player = null;
            }
        },
        replayback(url, playTimes) {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].destroy().then(() => {
                    this.initplayer();
                    this.playback(url, playTimes);
                });
            } else {
                this.initplayer();
                this.playback(url, playTimes);
            }
        },
        setPlaybackStartTime(curTime) {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].setPlaybackStartTime(curTime);
                this.playbackStartTime = curTime;
            }
        },
        destroy() {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].destroy().then(() => {
                    this.initplayer();
                });
            }
        },
        close() {
            if (jessibucaPlayer[this._uid]) {
                jessibucaPlayer[this._uid].close();
            }
        },
        getBroadcastStatus() {
            if (this.broadcastStatus == -2) {
                return 'primary';
            }
            if (this.broadcastStatus == -1) {
                return 'primary';
            }
            if (this.broadcastStatus == 0) {
                return 'warning';
            }
            if (this.broadcastStatus == 1) {
                return 'danger';
            }
        },
        broadcastStatusClick() {
            if (this.broadcastStatus == -1) {
                // 默认状态， 开始
                this.broadcastStatus = 0;
                // 发起语音对讲
                getPushUrl(this.deviceId, this.channelId).then((res) => {
                    console.log(res);
                    if (res.code === 200) {
                        let streamInfo = res.data;
                        if (document.location.protocol.includes('https')) {
                            this.startwebrtc(streamInfo.rtcs);
                        } else {
                            this.startwebrtc(streamInfo.rtc);
                        }
                    } else {
                        this.$message({
                            showClose: true,
                            message: res.msg,
                            type: 'error',
                        });
                    }
                });
            } else if (this.broadcastStatus === 1) {
                this.broadcastStatus = -1;
                this.broadcastRtc.close();
            }
        },
        startwebrtc(url) {
            // 获取推流鉴权Key
            this.broadcastRtc = new ZLMRTCClient.Endpoint({
                debug: true, // 是否打印日志
                zlmsdpUrl: url, //流地址
                simulecast: false,
                useCamera: false,
                audioEnable: true,
                videoEnable: false,
                recvOnly: false,
            });
            this.broadcastRtc.on(ZLMRTCClient.Events.WEBRTC_NOT_SUPPORT, (e) => {
                // 获取到了本地流
                console.error('不支持webrtc', e);
                this.$message({
                    showClose: true,
                    message: this.$t('views.components.player.webrtc.08878-6'),
                    type: 'error',
                });
                this.broadcastStatus = -1;
            });

            this.broadcastRtc.on(ZLMRTCClient.Events.WEBRTC_ICE_CANDIDATE_ERROR, (e) => {
                // ICE 协商出错
                console.error('ICE 协商出错');
                this.$message({
                    showClose: true,
                    message: this.$t('views.components.player.webrtc.08878-7'),
                    type: 'error',
                });
                this.broadcastStatus = -1;
            });

            this.broadcastRtc.on(ZLMRTCClient.Events.WEBRTC_OFFER_ANWSER_EXCHANGE_FAILED, (e) => {
                // offer anwser 交换失败
                console.error('offer anwser 交换失败', e);
                this.$message({
                    showClose: true,
                    message: this.$t('views.components.player.webrtc.08878-8') + e,
                    type: 'error',
                });
                this.broadcastStatus = -1;
            });
            this.broadcastRtc.on(ZLMRTCClient.Events.WEBRTC_ON_CONNECTION_STATE_CHANGE, (e) => {
                // offer anwser 交换失败
                console.log('状态改变', e);
                if (e === 'connecting') {
                    this.broadcastStatus = 0;
                } else if (e === 'connected') {
                    this.broadcastStatus = 1;
                    startBroadcast(this.deviceId, this.channelId).then((res) => {
                        if (res.code === 200) {
                            console.log('开始推流！');
                        }
                    });
                } else if (e === 'disconnected') {
                    this.broadcastStatus = -1;
                } else if (e === 'failed') {
                    this.broadcastStatus = -1;
                    console.log('状态改变', e);
                    this.$message({
                        showClose: true,
                        message: res.msg,
                        type: 'error',
                    });
                }
            });
            this.broadcastRtc.on(ZLMRTCClient.Events.CAPTURE_STREAM_FAILED, (e) => {
                // offer anwser 交换失败
                console.log('捕获流失败', e);
                this.$message({
                    showClose: true,
                    message: this.$t('views.components.player.webrtc.08878-9') + e,
                    type: 'error',
                });
                this.broadcastStatus = -1;
            });
        },

        stopBroadcast() {
            this.broadcastRtc.close();
            this.broadcastStatus = -1;
            stopBroadcast(this.deviceId, this.channelId).then((res) => {
                if (res.code == 200) {
                    this.broadcastStatus = -1;
                    this.broadcastRtc.close();
                } else {
                    this.$message({
                        showClose: true,
                        message: res.msg,
                        type: 'error',
                    });
                }
            });
        },
    },
};
</script>

<style scoped lang="scss">
.root {
    display: flex;
    margin-right: 3rem;
}

.container-shell {
    backdrop-filter: blur(5px);
    // background: hsla(0, 0%, 50%, 0.5);
    //background: #fff;
    //padding: 10px 4px 10px 4px;
    /* border: 2px solid black; */
    // width: auto;
    position: relative;
    border-radius: px2vw(10);
    // box-shadow: 0 5px 5px;
}

.container-shell:before {
    //content: "设备播放器";
    position: absolute;
    color: darkgray;
    //top: 4px;
    left: px2vw(10);
    //text-shadow: 1px 1px black;
}

#container {
    background: rgba(13, 14, 27, 0.7);
    width: px2vw(1200);
    height: px2vh(630);
    border-radius: 5px;
}

.err {
    position: absolute;
    top: px2vh(40);
    left: px2vw(10);
    color: red;
}

.option {
    position: absolute;
    top: px2vh(4);
    right: px2vw(10);
    display: flex;
    place-content: center;
    font-size: px2font(12);
}

.option span {
    color: white;
}

//@media (max-width: 720px) {
//    #container {
//        width: 90vw;
//        height: 52.7vw;
//    }
//}

/* 倍速控制按钮定位 */
.playback-rate-control {
    position: absolute;
    bottom: px2vh(5);
    right: px2vw(210);
    z-index: 100;
}

/* 当前选中项高亮 */
.selected {
    color: #409eff;
    font-weight: bold;
}

.player-video-container {
    width: 100%;
    height: 0;
    padding-bottom: 56.25%; /* 16:9 比例 */
    position: relative;
    background-color: #000;
}

.trank-wrap {
    position: absolute;
    right: px2vw(180); /* 根据实际情况调整位置 */
    bottom: px2vh(8);
    z-index: 10;
    color: #fff;
    cursor: pointer;
}

::v-deep .jb-pro-controls-playback-time-inner {
    width: px2vw(800) !important;
}
/* 控制按钮 */
.control-button {
    background: none;
    border: none;
    color: white;
    font-size: px2font(16);
    width: px2vw(22);
    height: px2vh(32);
    display: flex;
    align-items: center;
    justify-content: center;
    cursor: pointer;
    opacity: 0.8;
    transition: opacity 0.2s;
}

.control-button:hover {
    opacity: 1;
}

/* 倍速选择 */
.speed-dropdown {
    position: relative;
    margin-right: px2vw(10);
}

.speed-button {
    font-size: px2font(16);
    min-width: px2vw(35);
    justify-content: space-between;
}

.speed-menu {
    position: absolute;
    bottom: 100%;
    right: 0;
    background-color: rgba(0, 0, 0, 0.8);
    border-radius: px2vw(4);
    padding: px2vh(5) 0;
    width: px2vw(60);
    box-shadow: 0 2px 10px rgba(0, 0, 0, 0.3);
    display: none;
}

.speed-menu div {
    color: white;
    font-size: px2font(13);
    cursor: pointer;
    transition: background-color 0.2s;
}

.speed-menu div:hover {
    background-color: rgba(255, 255, 255, 0.1);
}

.speed-menu div.active {
    color: #ff0000;
    font-weight: 500;
}

.speed-dropdown:hover .speed-menu,
.speed-menu:hover {
    display: block;
}
</style>
